#include	"ordered_map.h"
#include	"common.h"


struct ordered_map create_ordered_map(u32int maxsize, lt_pred less_than){

	struct ordered_map tmap;

	tmap.array = (type_common *)kmalloc(sizeof(type_common) * maxsize);
	tmap.size = 0;
	tmap.maxsize = maxsize;
	tmap.less_than = less_than;
	memset(tmap.array, 0, sizeof(type_common) * maxsize);

	return tmap;
}

struct ordered_map place_ordered_map(u32int addr, u32int maxsize, lt_pred less_than){

	struct ordered_map tmap;

	monitor_write("[map] Placing map...");

	tmap.array = (void *)addr;

	monitor_write("at ");
	monitor_write_hex(tmap.array);
	monitor_write(", size = ");
	monitor_write_hex(sizeof(type_common) * maxsize);
	monitor_write("\n");

	monitor_write("[map] Initializing index structures...");
	monitor_write("range = ");
	monitor_write_hex((u32int)tmap.array + (u32int)sizeof(type_common) * maxsize);
	monitor_write("...");

	tmap.size = 0;
	tmap.maxsize = maxsize;
	tmap.less_than = less_than;

	memset(tmap.array, 0, sizeof(type_common) * maxsize);

	return tmap;
}

void destroy_ordered_map(struct ordered_map *map){
	
	/* test stub */
}

void insert_ordered_map(struct ordered_map *map, type_common ele){

	u32int iter, iter0;
	type_common tmp, tmp2;
	
	for(iter = 0; iter < map -> size && map -> less_than(map -> array[iter], ele); iter++)
		;
	if(iter == map -> size){
		map -> array[(map -> size)++] = ele;
		iter0 = iter;
	}else{
		tmp = map -> array[iter];
		map -> array[iter] = ele;
		iter0 = iter;
		while(iter < map -> size){
			tmp2 = map -> array[++iter];
			map -> array[iter] = tmp;
			tmp = tmp2;
		}
		(map -> size)++;
	}

}

void delete_ordered_map(struct ordered_map *map, u32int ind){

	u32int iter;
	type_common tmp;
/*
	monitor_write("[map] deleting an element...\n");
*/
	(map -> size)--;
	for(iter = ind; iter < map -> size; iter++)
		map -> array[iter] = map -> array[iter + 1];	
}

type_common lookfor_ordered_map(struct ordered_map *map, type_common ele){

	u32int iter;

	for(iter = 0; iter < map -> size && map -> array[iter] != ele; iter++)
		;
	if(iter == map -> size){
		return (type_common)0;
	}else{
		return map -> array[iter];
	}
}
